home *** CD-ROM | disk | FTP | other *** search
- /*
- * $Id: marking.c,v 0.91 1994/02/20 00:53:16 zhao Pre-Release $
- *
- *. This file is part of BIT shareware package. After the two weeks of
- * free evaluation period, you are encouraged (required) to register
- * your copy for a small registration fee, which is $35 for personal use
- * and $50 for commercial, government and institutional use.
- *
- * Copyright(c) 1993, 1994 by T.C. Zhao.
- * All rights reserved.
- *
- * Permission to use, copy, and distribute this software in its entirety
- * for non-commercial purposes is hereby granted, provided that the
- * above shareware and copyright notices and this permission notice
- * appear in all copies and their documentation.
- *
- * This software may be modified for your own use, but modified versions
- * may not be distributed without prior consent of the author.
- *
- * This software is provided "as is" without expressed or implied
- * warranty of any kind.
- *
- *.
- *
- * Purpose:
- * Place various simple geometric figures into image. The bitmaps is
- * in bm.h while the actual drawing routine in gl_util.c and ps.c.
- * It is sort of bad that all locations refers to the CENTER of the
- * sgfs and NOT the lower left corner.
- *
- * Code is a little more complicated than it should be because
- * doublebuffering in over/pup is generally not supported in hardware.
- * Need to simulate it. It appear working ok, but speed is not too good.
- */
-
- #if !defined(lint) && defined(F_ID)
- char *id_mk = "$Id: marking.c,v 0.91 1994/02/20 00:53:16 zhao Pre-Release $";
- #endif
-
- #include "bit.h"
- #include "extern.h"
- #include "bm.h" /* the bitmaps. */
-
- /******************* Limits and defines **********************/
-
-
- /********************************************************
- * If NO_OP_DBL is defined, double buffer simulation in
- * over/pup plane will be suppressed.
- ********************************************************/
-
- /* #define NO_OP_DBL */
-
- #define MAXOBJS 25 /* max no. of different objects */
- #define MAXOSIZE 600 /* max size of the objects */
- #define MAXSAVE 101 /* max no. of objs per image */
-
- /*************** Local varialbes, excluding GUI *************/
-
- static float mapx = 1.0, mapy = 1.0;
- static int pixels = 1; /* units of measurement */
- static int orix, oriy; /* origin of measurement */
- static int x, y; /* position relative to window */
- static int w = 20, h = 20; /* current size in pixels */
- static int angle, langle; /* angle of rotation, deci-degree */
- static int lx, ly, lw, lh; /* last position and size */
- static int lwidth = 1; /* line width */
- static int llwidth = 1; /* line width */
- static int bcolor = 1; /* over/pup index used */
- static int xy = 1; /* if keep aspect ratio */
- static int reportr; /* distance reporting */
- static int immediate = 1; /* rendering method */
-
- /* Default color */
- static int dcol[] =
- {
- 0xff, 0xff, 0, 0
- };
-
- /*********** local functions and structures *******************/
-
- typedef void (*GL_draw) (int, int, int, int, int, int);
- typedef const char *PS_draw;
-
- static void mark_move(void);
- static void mark_moving(long);
- static void mark_events(IPTR, long, short);
- static int mark_wm_event(IPTR, int);
- static void mark_draw(int, int);
- static void mark_doit(IPTR, int, int, int, int);
-
- /* Structure for simple geometric figures */
- typedef struct
- {
- const char *name; /* name. Must not be null */
- char *bits; /* bitmaps for the sgf */
- GL_draw how; /* GL drawing routine */
- const char *psdraw; /* PS drawing commands */
- int fill; /* If filled sgf */
- }
- Obj_t;
-
- /**************************************************************/
- /* all PostScript drawings are defined in ps.c. */
- extern const char ps_plus[];
- extern const char ps_circ[], ps_rect[];
- extern const char ps_tri[], ps_star[];
- extern const char ps_arrow[], ps_hdist[], ps_line[];
-
- /****** All objects definations ********************************/
-
- static const Obj_t objs[] =
- {
- {"Plus", plus_bits, gl_plus, ps_plus, 0}, /* plus */
- {"Hdist", hdist_bits, gl_hdist, ps_hdist, 0}, /* |---| */
- {"Delta", tri_bits, gl_tri, ps_tri, 0}, /* triangle */
- {"DeltaF", ftri_bits, gl_tri, ps_tri, 1}, /* filled */
- {"Circ", circ_bits, gl_circ, ps_circ, 0}, /* circle */
- {"CircF", fcirc_bits, gl_circ, ps_circ, 1}, /* filled */
- {"Rect", rect_bits, gl_rect, ps_rect, 0}, /* rectangle */
- {"RectF", frect_bits, gl_rect, ps_rect, 1}, /* filled */
- {"Star", star_bits, gl_star, ps_star, 0},
- {"StarF", fstar_bits, gl_star, ps_star, 1},
- {"Arrow", arrow_bits, gl_arrow, ps_arrow, 1},
- {"Line", line_bits, gl_line, ps_line, 0}
- };
-
- static int totalobjs = sizeof(objs) / sizeof(objs[0]);
- static int currentobj, cfill;
- static GL_draw cdraw; /* curerent drawing routine */
-
- /*********** GUI stuff ***************************************/
- static FL_FORM *tobj;
-
- /* create the forms containing bitmaps for the symbols */
- static void create_form_tobj(void);
- static void handle_bmcb(FL_OBJECT * ob, long p);
- static void save_it(int, int, int, int, int, int, rgba_t, ci_t);
- static void show_map_unit(float, float);
- static void report_distance(int, int);
- static void report_size(int, int);
- static void report_rotation(float);
- static void save_bcolor(void);
- static void restore_bcolor(void);
- static void origin_cb(FL_OBJECT *, long);
- static void map_slider(void);
-
- /********************************************************************
- * non-interactively set origin. Always relative to ll corner of img
- **********************************************************************/
- static int niorix, nioriy;
-
- void
- set_marking_origin(int ox, int oy)
- {
- niorix = ox;
- nioriy = oy;
- }
-
-
- /***********************************************************************
- * mark specific position within the image with simple geometric figures
- * Global entry point
- ************************************************************************/
- int
- img_marking(IPTR im)
- {
- short val;
- long dev;
-
- cdraw = objs[currentobj].how;
- cfill = objs[currentobj].fill;
-
- if (bcolor >= over_pup_colors)
- bcolor = over_pup_colors - 1;
-
- if (bcolor == 0) /* avoid interference with WM */
- bcolor = 1;
- save_bcolor();
-
- set_use_calloc(1);
-
- /* how to handle window resize, repositioning */
- install_wm_handler(mark_wm_event);
-
- /* initialize position */
- mark_wm_event(im, 0);
-
- create_form_tobj();
- show_map_unit(mapx, mapy);
-
- /* do this to get origin right */
- x = niorix + im->xi;
- y = nioriy + im->yi;
- origin_cb(0, 0);
-
- bit_show_form(tobj, FL_PLACE_MOUSE, 0, "Objects");
-
- handle_bmcb(0, currentobj);
- mark_draw(currentobj, bcolor);
-
- report_distance(x, y);
-
- while ((dev = bit_qread(&val)) != KEYBD || val != 27)
- mark_events(im, dev, val);
-
- /* done. Clean up */
-
- clear_over_pup();
- remove_wm_handler(mark_wm_event);
- bit_hide_form(tobj);
- set_current_window(win_id);
- drawmode(NORMALDRAW);
- linewidth(1); /* line width is shared among all buffers */
- restore_bcolor();
- hide_rect_size();
- hide_mouse_position();
- set_use_calloc(0);
- hide_getcolor();
- return 0;
- }
-
- /*********************************************************
- * Save current position
- *********************************************************/
- static void
- save_position(void)
- {
- lx = x;
- ly = y;
- lw = w;
- lh = h;
- llwidth = lwidth;
- langle = angle;
- }
-
-
- /**********************************************************
- * given a name, find index
- ************************************************************/
- static int
- sgf_get_index(const char *p)
- {
- int i, k;
-
- if (!p || !*p)
- return 0;
-
- for (i = k = 0; !k && i < totalobjs; i++)
- k = strcmp(objs[i].name, p) == 0;
-
- return k ? --i : 0;
- }
-
-
- /**********************************************************
- * Global routine that set the units of measure
- ***********************************************************/
- void
- set_marking_units(float mx, float my)
- {
- if (mx > 0.0)
- mapx = mx;
- if (my > 0.0)
- mapy = my;
- }
-
- /******************************************************************
- * Clear up the old one and draw a new one. No set_current_windows, no
- * buffer switch etc.
- *****************************************************************/
- static void
- mark_draw_only(int ind, int bc)
- {
- static int lastind;
- int noclear;
-
-
- /* if same object but larger, there is no need to clear screen. */
- noclear = (ind == lastind) &&
- (langle == angle) &&
- (lwidth >= llwidth) &&
- (lx == x) && (ly == y) && (lw <= w) && (lh <= h) && cfill;
-
- /* arrow is a special case: it has cfill but not really filled */
- if (!noclear || cdraw == gl_arrow)
- {
- color(0);
- cdraw(lx, ly, lw, lh, cfill, langle);
- currentobj = ind;
- cfill = objs[ind].fill;
- cdraw = objs[ind].how;
- }
- lastind = ind;
-
- /* draw the new one */
- color(bc);
- cdraw(x, y, w, h, cfill, angle);
- save_position();
- }
-
- #ifndef NO_OP_DBL
- static void mark_rasterize(void);
- #else
- #define mark_rasterize()
- #endif
-
- /**********************************************************************
- * Draw the current object in the over/pup plane and taking care of
- * window and framebuffer as well
- *********************************************************************/
- static void
- mark_draw(int ind, int bc)
- {
- long owin = winget();
-
- set_current_window(win_id);
- reshapeviewport();
- switch_frame_buffer();
- linewidth(lwidth);
-
- mark_draw_only(ind, bc);
-
- mark_rasterize();
-
- set_current_window(win_id);
- reshapeviewport();
- drawmode(NORMALDRAW);
- set_current_window(owin);
- }
-
- /*******************************************************************
- * Do a complete draw after refreshing over/pup plane
- *******************************************************************/
- static void
- complete_draw(int ind, int bc)
- {
- clear_over_pup();
- set_current_window(win_id);
- switch_frame_buffer();
- linewidth(lwidth);
-
- currentobj = ind;
- cfill = objs[ind].fill;
- cdraw = objs[ind].how;
-
- color(bc);
- cdraw(x, y, w, h, cfill, angle);
- mark_rasterize();
-
- save_position();
- set_current_window(win_id);
- drawmode(NORMALDRAW);
- }
-
- /************************************************************
- * handle window re-size and reposition events
- *************************************************************/
- static int
- mark_wm_event(IPTR im, int wm)
- {
- static int imxi, imyi;
-
- if (!wm)
- {
- x = lx = (im->xi > 0) ? im->xi : 1;
- y = ly = (im->yi > 0) ? im->yi : 1;
- if (IS_CI(im))
- {
- dcol[3] = im->cmap->colors - 2;
- dcol[0] = im->cmap->ct[0][dcol[3]];
- dcol[1] = im->cmap->ct[1][dcol[3]];
- dcol[2] = im->cmap->ct[2][dcol[3]];
- }
- }
- else
- {
- /* x and y must be unchanged relative to image */
- x += (im->xi - imxi);
- y += (im->yi - imyi);
- complete_draw(currentobj, bcolor);
- }
- imxi = im->xi;
- imyi = im->yi;
- return 0;
- }
-
- /*****************************************************************
- * How to handle keyboad events
- ****************************************************************/
- static long
- mark_keybd(int val)
- {
- int ret = 0;
- static int step = 1;
- int re_ras = 0; /* if re-rasterize the object */
-
- switch (val)
- {
- case 'r':
- angle -= step * 10;
- if (angle < -3600)
- angle += 3600;
- re_ras = 1;
- break;
- case 'R':
- angle += step * 10;
- if (angle > 3600)
- angle -= 3600;
- re_ras = 1;
- break;
- case 'x':
- if ((w -= step) < 1)
- w = 1;
- re_ras = 1;
- break;
- case 'X':
- if ((w += step) > MAXOSIZE)
- w = MAXOSIZE;
- re_ras = 1;
- break;
- case 'y':
- if ((h -= step) < 1)
- h = 1;
- re_ras = 1;
- break;
- case 'Y':
- if ((h += step) > MAXOSIZE)
- h = MAXOSIZE;
- re_ras = 1;
- break;
- case 'h':
- case 'H':
- x -= step;
- break;
- case 'L':
- case 'l':
- x += step;
- break;
- case 'j':
- case 'J':
- y -= step;
- break;
- case 'K':
- case 'k':
- y += step;
- break;
- default:
- if (val > '0' && val <= '9')
- step = val - '0';
- else
- ret = val;
- break;
- }
-
- if (re_ras)
- {
- mark_draw(currentobj, bcolor);
- report_rotation(0.1 * angle);
- report_size(w, h);
- }
- else
- mark_move();
- return ret;
- }
-
- /***********************************************************************
- * All GL events
- *********************************************************************/
- /* ARGSUSED */
- static void
- mark_events(IPTR im, long dev, short val)
- {
- switch (dev)
- {
- case KEYBD:
- mark_keybd(val);
- break;
- case UPARROWKEY:
- if (val)
- mark_keybd('k');
- break;
- case DOWNARROWKEY:
- if (val)
- mark_keybd('j');
- break;
- case LEFTARROWKEY:
- if (val)
- mark_keybd('h');
- break;
- case RIGHTARROWKEY:
- if (val)
- mark_keybd('l');
- break;
- case LEFTMOUSE:
- case MIDDLEMOUSE:
- if (val)
- mark_moving(dev);
- break;
- default:
- break;
- }
- }
-
- #ifdef NO_OP_DBL
- #define dbl_mark_move sgl_mark_move
- #define dbl_mark_moving sgl_mark_moving
- #else
- /*****************************************************************
- * Get current object in rasterized form.
- * feedback should be the way to get the rasterized object, but it
- * is not portable, too lazy to do it. Cheat here
- ******************************************************************/
- static ci_t **cfig;
- static int objbw, objbh;
-
- static void
- mark_rasterize(void)
- {
- int bx, by, bw, bh;
- register ci_t *s;
- static int lastrasw, lastrash, lastlwidth;
- static int lastrotate;
- static GL_draw lastdraw;
- static int incomplete;
- int halflw = (lwidth + 1) / 2;
- int sameobj, openobj;
-
- if (!simu_op_dblbuf)
- return;
-
- /* check if same object */
- sameobj = (lastlwidth == lwidth) &&
- (lastrotate == angle) &&
- (lastrasw == w && lastrash == h) &&
- (lastdraw == cdraw);
-
- openobj = (cfill == 0 || cdraw == gl_arrow);
-
- if ((openobj || sameobj) && !incomplete)
- return;
-
- find_bbox(x - halflw, y - halflw, w + (lwidth + 1), h + (lwidth + 1),
- 0.1 * angle, &bx, &by, &bw, &bh);
-
- bh += lwidth + 1;
- bw += lwidth + 1;
-
- /* it is important to center (x,y) */
- bx = x - (bw / 2);
- by = y - (bh / 2);
-
- /* get buffer for the rasterized object */
- if (cfig)
- free_mat(cfig);
- cfig = get_mat(bh, bw, sizeof(**cfig));
-
- rectread(bx, by, bx + bw - 1, by + bh - 1, cfig[0]);
-
- incomplete = (bx <= 0 || (bx + bw - 1) >= win_w ||
- (by <= 0 || (by + bh - 1) >= win_h));
-
- /* mask off the garbarge */
- s = cfig[0] + bw * bh;
- while (--s >= cfig[0])
- *s = ((*s & bcolor) != bcolor) ? 0 : bcolor;
-
- objbw = bw;
- objbh = bh;
- lastrasw = w;
- lastrash = h;
- lastdraw = cdraw;
- lastrotate = angle;
- lastlwidth = lwidth;
-
- #ifdef MDEBUG
- M_debug("MarkRasterize", "Done");
- #endif
-
- }
-
- /****************************************************************
- * Move mark without flickering, i.e., simulating double buffering.
- * Doesn't take care window, buffer etc.
- * (x,y) new location
- ****************************************************************/
- static void
- dbl_mark_move(void)
- {
- int x1, x2, y1, y2;
- static ci_t **scrn;
- int sw, sh;
- int halfw = objbw / 2 + 1, halfh = objbh / 2 + 1;
-
- x1 = Min(lx, x) - 1;
- x2 = Max(lx, x) + 1;
-
- y1 = Min(ly, y) - 1;
- y2 = Max(ly, y) + 1;
-
- sw = x2 - x1 + 1 + objbw + 2;
- sh = y2 - y1 + 1 + objbh + 2;
-
- (report_mouse ? show_mouse_position : report_distance) (x, y);
-
- if (scrn)
- free_mat(scrn);
-
- scrn = get_mat(sh, sw, sizeof(ci_t));
-
- put_submat(scrn, sh, sw, cfig, (y - y1) + 1, (x - x1) + 1,
- objbh, objbw, sizeof(ci_t));
-
- x1 -= halfw;
- y1 -= halfh;
-
- rectwrite(x1, y1, x1 + sw - 1, y1 + sh - 1, scrn[0]);
- save_position();
- }
-
- /********************************************************************
- * Simulate a double buffer in over/pup plane
- *******************************************************************/
- static void
- dbl_mark_moving(long dev)
- {
- do
- {
- get_mouse(&x, &y);
- x -= win_xo;
- y -= win_yo;
- if (lx - x || ly - y)
- dbl_mark_move();
- }
- while (getbutton(dev));
-
- #ifdef MDEBUG
- M_debug("MoveMark", "Simulated doublebuffer");
- #endif
-
- }
-
- #endif /* NO_OP_DBL */
-
- /***********************************************************
- * Continuously move mark as long as mouse is down
- ***********************************************************/
-
- static void
- sgl_mark_move(void)
- {
- /* draw it will set lx, ly */
- mark_draw_only(currentobj, bcolor);
- (report_mouse ? show_mouse_position : report_distance) (x, y);
- }
-
- static void
- sgl_mark_moving(long dev)
- {
- do
- {
- get_mouse(&x, &y);
- x -= win_xo;
- y -= win_yo;
- if (x - lx || y - ly)
- {
- (report_mouse ? show_mouse_position : report_distance) (x, y);
- mark_draw(currentobj, bcolor);
- }
- }
- while (getbutton(dev));
-
- #ifdef MDEBUG
- M_debug("MoveMark", "single");
- #endif
-
- }
-
-
- /*************************************************************
- * Dragging the current object
- *************************************************************/
-
- static void
- mark_moving(long dev)
- {
- /* another chance to re-rasterize */
- get_mouse(&x, &y);
- x -= win_xo;
- y -= win_yo;
- mark_draw(currentobj, bcolor);
-
- set_current_window(win_id);
- switch_frame_buffer();
- ((cfill && cdraw != gl_arrow && simu_op_dblbuf && cfig) ?
- dbl_mark_moving : sgl_mark_moving) (dev);
- set_current_window(win_id);
- drawmode(NORMALDRAW);
- }
-
- /******************************************************************
- * move current object to a new location
- ******************************************************************/
-
- static void
- mark_move(void)
- {
- set_current_window(win_id);
- switch_frame_buffer();
- ((cfill && simu_op_dblbuf) ? dbl_mark_move : sgl_mark_move) ();
- drawmode(NORMALDRAW);
- }
-
- static FL_OBJECT *bms[MAXOBJS], *hb[MAXOBJS], *sl[2];
- static FL_OBJECT *otext, *rtext, *dtext;
- static int totalshown, offset;
- static FL_OBJECT *ix, *iy, *mxi, *myi, *ingrp;
- #define FL_BMCOLOR 520
-
- static void
- show_map_unit(float mx, float my)
- {
- fl_set_input(mxi, ftoa(mx, 5));
- fl_set_input(myi, ftoa(my, 5));
- }
-
- /*********************************************************************
- * report distance from the origin: Here xx & yy are the mouse position
- * relative to window.
- *********************************************************************/
-
- #include <math.h>
- static void
- report_distance(int xx, int yy)
- {
- float dx, dy;
-
- fl_freeze_form(tobj);
- if (pixels)
- { /* absolute coordinates */
- fl_set_input(ix, itoa((xx - orix)));
- fl_set_input(iy, itoa((yy - oriy)));
- dx = (xx - orix);
- dy = (yy - oriy);
- }
- else
- { /* user coord */
- dx = mapx * (xx - orix);
- dy = mapy * (yy - oriy);
- fl_set_input(ix, ftoa(dx, 5));
- fl_set_input(iy, ftoa(dy, 5));
- }
- fl_unfreeze_form(tobj);
-
- if (reportr)
- fl_set_object_label(dtext, ftoa(sqrt(dx * dx + dy * dy), 2));
- }
-
- /*************************************************************
- * Show object in current selected units
- ************************************************************/
-
- static void
- report_size(int width, int height)
- {
-
- fl_freeze_form(tobj);
- if (pixels)
- {
- fl_set_slider_value(sl[0], width);
- fl_set_slider_value(sl[1], height);
- }
- else
- {
- fl_set_slider_value(sl[0], mapx * width);
- fl_set_slider_value(sl[1], mapy * height);
- }
- fl_unfreeze_form(tobj);
- }
-
-
- /*********************************************************************
- * draw the object in normal buffer, relative to image, in units of pixels
- *
- **********************************************************************/
- static void
- mark_doit(IPTR im, int xx, int yy, int ww, int hh)
- {
- long owin = winget();
- rgba_t cc = Pack(dcol[0], dcol[1], dcol[2]);
- int bx, by, bw, bh, halflw;
-
-
- set_current_window(win_id);
- drawmode(NORMALDRAW);
- reshapeviewport();
-
- linewidth(lwidth);
-
- smooth_line_on(im, dcol, lwidth);
-
- cdraw(xx, yy, ww, hh, cfill, angle);
-
- #ifndef SGL_BUF
- if (doublebuffer)
- {
- swapbuffers();
- cdraw(xx, yy, ww, hh, cfill, angle);
- }
- #endif
-
- if (immediate)
- {
- /* if immediate, read the framebuffer */
- halflw = (lwidth) / 2;
- find_bbox(xx - halflw, yy - halflw, ww + lwidth, hh + lwidth,
- 0.1 * angle, &bx, &by, &bw, &bh);
- bx -= halflw;
- by -= halflw;
- bw += lwidth;
- bh += lwidth;
- fb_to_ras(im, make_rect(bx, by, bw, bh));
- }
- else
- {
- /* save current figure */
- save_it(currentobj, xx - im->xi, yy - im->yi, ww, hh,
- lwidth, cc, dcol[3]);
- }
-
- smooth_line_off(im, dcol);
- clear_over_pup();
-
- set_current_window(owin);
- }
-
- /* A dummy function to get call back prototype right */
- /* ARGSUSED */
- static void
- doit(FL_OBJECT * ob, long p)
- {
- int xx = x, yy = y;
- mark_doit(imgptr, xx, yy, w, h);
- }
-
- /******************************************************
- * User input for units
- ******************************************************/
-
- #include <stdlib.h>
- static void
- map_cb(FL_OBJECT * ob, long p)
- {
- const char *q = fl_get_input(ob);
- float tmp;
-
- if (p == 1)
- {
- if ((tmp = atof(q)) <= 0.0)
- {
- fl_set_input(ob, ftoa(mapx, 5));
- tmp = mapx;
- }
- mapx = tmp;
- }
- else
- {
- if ((tmp = atof(q)) <= 0.0)
- {
- fl_set_input(ob, ftoa(mapy, 5));
- tmp = mapy;
- }
- mapy = tmp;
- }
- if (!pixels)
- map_slider();
- report_distance(x, y);
- }
-
- /***************************************************************
- * With the given units and MAXOBJSIZE, set the slider
- ***************************************************************/
- #include <math.h>
- static void
- map_slider(void)
- {
- int xp, yp;
-
- fl_freeze_form(tobj);
- if (!pixels)
- { /* use user coordinates system */
- xp = (mapx < 1.0) ? -(log10(mapx) - 0.95) : 0;
- yp = (mapy < 1.0) ? -(log10(mapy) - 0.95) : 0;
- fl_set_slider_precision(sl[0], xp);
- fl_set_slider_precision(sl[1], yp);
- fl_set_slider_step(sl[0], mapx);
- fl_set_slider_step(sl[1], mapy);
- fl_set_slider_bounds(sl[0], 0.0, (mapx * MAXOSIZE));
- fl_set_slider_bounds(sl[1], 0.0, (mapy * MAXOSIZE));
- fl_set_slider_value(sl[0], (mapx * w));
- fl_set_slider_value(sl[1], (mapy * h));
- }
- else
- {
- fl_set_slider_precision(sl[0], 0);
- fl_set_slider_precision(sl[1], 0);
- fl_set_slider_step(sl[0], 1);
- fl_set_slider_step(sl[1], 1);
- fl_set_slider_bounds(sl[0], 0.0, MAXOSIZE);
- fl_set_slider_bounds(sl[1], 0.0, MAXOSIZE);
- fl_set_slider_value(sl[0], w);
- fl_set_slider_value(sl[1], h);
- }
- fl_unfreeze_form(tobj);
- }
-
- /***************************************************************
- * A new location is input from keyboard
- **************************************************************/
- static void
- position_cb(FL_OBJECT * ob, long p)
- {
- const char *q = fl_get_input(ob);
- float xx, yy;
-
- if (p == 0)
- {
- xx = atof(q);
- x = pixels ? (xx + 0.5) : (xx / mapx + 0.5);
- x += orix;
- }
- else
- {
- yy = atof(q);
- y = pixels ? (yy + 0.5) : (yy / mapy + 0.5);
- y += oriy;
- }
- mark_draw(currentobj, bcolor);
- }
-
-
- /*********************************************************************
- * Since bcolor is an index in over/pup plane and we will map it
- * to different colors, better save it
- *******************************************************************/
- static short bc[3];
-
- static void
- save_bcolor(void)
- {
- switch_frame_buffer();
- getmcolor(bcolor, bc, bc + 1, bc + 2);
-
- /* default drawing color */
- mapcolor(bcolor, dcol[0], dcol[1], dcol[2]);
- drawmode(NORMALDRAW);
- }
-
- static void
- restore_bcolor(void)
- {
- switch_frame_buffer();
- mapcolor(bcolor, bc[0], bc[1], bc[2]);
- drawmode(NORMALDRAW);
- }
-
-
-
- /* ARGSUSED */
- static void
- handle_bmcb(FL_OBJECT * ob, long p)
- {
- static int last = -1;
-
- if (last >= 0)
- {
- fl_set_object_color(bms[last], FL_BLACK, FL_MAGIC1);
- fl_redraw_object(bms[last]);
- }
- last = p;
- fl_set_object_color(bms[p], FL_BMCOLOR, FL_MAGIC2);
- fl_redraw_object(bms[p]);
- complete_draw(p + offset, bcolor);
- }
-
- /******************************************************************/
-
- /* routines related to saving and displaying by other routines */
- typedef struct
- {
- int obj; /* index into the struct */
- int x, y, w, h, t; /* dimensions */
- int angle; /* in tenth of degrees */
- rgba_t color; /* color of obj */
- ci_t ci; /* color index */
- }
- Save_obj;
-
- static int totalsave;
-
- /*
- * by defining saveobj to be pointers, we can save about 20 bytes each, or
- * MAXSAVE * 20, or 2K, not worth it
- */
-
- static Save_obj saveobj[MAXSAVE];
-
- /****************************************************************
- * Save current objects
- ****************************************************************/
- static void
- save_it(int ind, int cx, int cy, int cw, int ch, int t,
- rgba_t c, ci_t ci)
- {
- Save_obj *p = saveobj + totalsave;
-
- p->obj = ind;
- p->x = cx;
- p->y = cy;
- p->w = cw;
- p->h = ch;
- p->color = c;
- p->ci = ci;
- p->t = t;
- p->angle = angle;
- if (++totalsave >= MAXSAVE)
- totalsave = MAXSAVE - 1;
- }
-
- /**************************************************************
- * Global routine to display all saved SGFs
- *************************************************************/
- void
- display_sgf(IPTR im)
- {
- long owin;
- Save_obj *p = saveobj, *ps;
- const Obj_t *ob;
- int xi, yi;
- int olwidth = lwidth;
- int cc[4];
-
-
- if (!totalsave || !im || !im->ok)
- return;
-
- owin = winget();
- set_current_window(win_id);
- reshapeviewport();
- xi = im->xi;
- yi = im->yi;
-
- /*
- * it is sort of bad that we have to turn anti-aliasing on and off, but
- * have no choice lwidth != 1 does not work right
- */
-
- for (ps = p + totalsave; p < ps; p++)
- {
- set_current_window(win_id);
- linewidth(p->t);
- lwidth = p->t;
- cc[4] = p->ci;;
- Unpack(p->color, cc[0], cc[1], cc[2]);
- smooth_line_on(im, cc, lwidth);
- ob = objs + p->obj;
- ob->how(p->x + xi, p->y + yi, p->w, p->h, ob->fill, p->angle);
- smooth_line_off(im, cc);
- }
-
- /* must restore width to 1 */
- linewidth(1);
- set_current_window(owin);
- lwidth = olwidth;
- }
-
- /*********************************************************************
- * Write to and Read from disk the sgf
- *********************************************************************/
-
- void
- dump_sgf(FILE * fp)
- {
- Save_obj *p = saveobj, *ps;
-
- fprintf(fp, "#SG %d\n", totalsave);
- fputs("Obj x y w h t r g b ci rot. Note (x,y) refers sgf's center\n", fp);
-
- for (ps = p + totalsave; p < ps; p++)
- {
- fprintf(fp, "#%s %d %d %d %d %d\n", objs[p->obj].name,
- p->x, p->y, p->w, p->h, p->t);
- fprintf(fp, "%g %g %g %d \n", C2NC(get_R(p->color)),
- C2NC(get_G(p->color)), C2NC(get_B(p->color)), (int) p->ci);
- fprintf(fp, "%d \n", p->angle);
- }
- }
-
- /**********************************************************************
- * Read in SGFs written by dump_sgf
- **********************************************************************/
- void
- load_sgf(IPTR im)
- {
- int n, r, g, b, ci;
- Save_obj *p = saveobj + totalsave, *ps;
- char buf[100], nm[40];
- FILE *fp = im->fp;
- /* by using this, we can change Save_obj freely */
- int hx, hy, hw, hh, ht;
-
- while ((n = getc(fp)) != EOF && n != '#')
- ;
- if (n != '#' || (n = getc(fp)) != 'S' || (n = getc(fp)) != 'G')
- return;
-
- n = readint(fp);
- if (n <= 0)
- return;
-
- if (n >= MAXSAVE)
- {
- Bark("LoadSgf", "Too many of them. Keeping %d", MAXSAVE);
- n = MAXSAVE;
- return;
- }
- M_info("LoadSGF", "Total %d sgfs found", n);
-
- for (ps = p + n; p < ps; p++)
- {
- while (fgets(buf, sizeof(buf) - 1, fp) && buf[0] != '#')
- ;
- if (buf[0] != '#') /* premature EOF */
- break;
- sscanf(buf + 1, "%s %d %d %d %d %d", nm, &hx, &hy, &hw, &hh, &ht);
- p->x = hx;
- p->y = hy;
- p->w = hw;
- p->h = hh;
- p->t = ht;
- r = (readfloat(fp) * PCMAXV + 0.4);
- g = (readfloat(fp) * PCMAXV + 0.4);
- b = (readfloat(fp) * PCMAXV + 0.4);
- p->color = Pack(r, g, b);
- ci = readpint(fp);
- p->ci = ci;
- if (ci < 0 || ci >= MAXCML)
- p->ci = 0;
- p->angle = readint(fp);
- p->obj = sgf_get_index(nm);
- }
- totalsave += n;
- }
-
- /********************************************************************
- * we only need to take care the RGB case because colormapped case
- * will be taken care of automatically by system colormap
- ********************************************************************/
- void
- sgf_to_gray(void)
- {
- register int q;
- register Save_obj *p = saveobj, *ps;
-
- for (ps = p + totalsave; p < ps; p++)
- {
- q = cpack2gray(p->color);
- p->color = Pack(q, q, q);
- }
- }
-
- /* take care of from RGB -> ci */
- void
- sgf_to_cmap(void)
- {
- register Save_obj *p = saveobj, *ps;
-
- if (!IS_CI(imgptr))
- return;
- for (ps = p + totalsave; p < ps; p++)
- p->ci = cmap_closematch(imgptr->cmap,
- get_R(p->color), get_G(p->color), get_B(p->color));
-
- }
-
- void
- del_marking(void)
- {
- totalsave = 0;
- return;
- }
-
- /*********************************************************
- * Routines to get info for format capable of vectors
- *************************************************************/
-
- int
- number_of_sgf(void)
- {
- return totalsave;
- }
-
- const char *
- sgf_name(int n)
- {
- return (saveobj[n].obj + objs)->name;
- }
-
- const char *
- sgf_psdraw(int n)
- {
- return (saveobj[n].obj + objs)->psdraw;
- }
-
- /******************************************************************
- * important info about an sgf: (x,y), (w,h), line width, closed path
- * and rotation angle
- *******************************************************************/
- void
- get_sgf_info(int n, int *xl, int *yl,
- int *wd, int *ht, int *t, int *fi, int *a)
- {
-
- Save_obj *p = saveobj + n;
-
- if (n < 0 || n >= totalsave)
- return;
-
- *xl = p->x;
- *yl = p->y;
- *wd = p->w;
- *ht = p->h;
- *t = p->t;
- *a = (0.1 * p->angle);
- *fi = ((objs + saveobj[n].obj)->fill) != 0;
- }
-
- /*********************************************************************
- * in order to find the bounding box correctly, we need info about the
- * dimensions of all sgfs that sticks out of the image. Only return the abs
- * value of the portion that sticks out. Rotation is not considered which
- * could cause some error, but typically sgf's are small enuf to ignore it.
- *********************************************************************/
-
- void
- get_sgf_bounds(IPTR im, int *top, int *left, int *bottom, int *right)
- {
- Save_obj *p = saveobj, *ps;
- int l = 0, b = 0, r = im->w, t = im->h;
- int w2, h2;
-
- for (ps = p + totalsave; p < ps; p++)
- {
- h2 = p->h / 2;
- w2 = p->w / 2;
- if (l > p->x - w2)
- l = p->x - w2;
- if (b > p->y - h2)
- b = p->y - h2;
- if (r < p->x + w2)
- r = p->x + w2;
- if (t < p->y + h2)
- t = p->y + h2;
- }
- /* return abs */
- *left = -l;
- *bottom = -b;
- *right = r - im->w;
- *top = t - im->h;
- }
-
- void
- get_sgf_color(int n, int *r, int *g, int *b)
- {
- int i;
-
- if (!imgptr)
- return;
- if (IS_CI(imgptr))
- {
- i = saveobj[n].ci;
- *r = imgptr->cmap->ct[0][i];
- *g = imgptr->cmap->ct[1][i];
- *b = imgptr->cmap->ct[2][i];
- }
- else
- {
- Unpack(saveobj[n].color, *r, *g, *b);
- }
- }
-
- /* ARGSUSED */
- static void
- del_dummy(FL_OBJECT * p, long q)
- {
- del_marking();
- imgptr->io->display(imgptr, 0, 1);
- }
-
- /*******************************************************************
- * Flip thru all defined objects.
- * Should never been called if obj is less than that can be shown
- ********************************************************************/
- /* ARGSUSED */
- static void
- more_cb(FL_OBJECT * ob, long p)
- {
- int i;
-
- if (offset + totalshown < totalobjs)
- offset += totalshown;
- else if (offset >= totalshown)
- offset -= totalshown;
-
- fl_freeze_form(tobj);
- for (i = 0; i < totalshown && i + offset < totalobjs; i++)
- {
- fl_show_object(bms[i]);
- fl_activate_object(hb[i]);
- if (i + offset != currentobj)
- fl_set_object_color(bms[i], FL_BLACK, FL_MAGIC1);
- else
- fl_set_object_color(bms[i], FL_BMCOLOR, FL_MAGIC2);
- fl_set_bitmap(bms[i], BM_W, BM_H, objs[i + offset].bits);
- }
- for (; i < totalshown; i++)
- {
- fl_hide_object_only(bms[i]);
- fl_deactivate_object(hb[i]);
- }
- fl_unfreeze_form(tobj);
- }
-
- /*****************************************************
- * aspect ratio and coordinate system switch
- ******************************************************/
- static void
- misc_cb(FL_OBJECT * ob, long p)
- {
- if (p == 2)
- { /* aspect ration of obj */
- xy = fl_get_choice(ob) - 1;
- }
- else
- {
- pixels = fl_get_choice(ob) - 1;
- map_slider();
- report_distance(x, y);
- }
- }
-
- /* ARGSUSED */
- static void
- dist_cb(FL_OBJECT * ob, long p)
- {
- reportr = fl_get_button(ob);
- }
-
- /****************************************************************
- * Set origin of measurement
- ***************************************************************/
- /* ARGSUSED */
- static void
- origin_cb(FL_OBJECT * ob, long p)
- {
- char ori[50];
-
- /* get the current position in pixels */
- orix = x;
- oriy = y;
- sprintf(ori, "%d,%d", orix, oriy);
- fl_set_object_label(otext, ori);
- report_distance(x, y);
- }
-
- /*******************************************************************
- * Select rendering method
- ******************************************************************/
- /*ARGSUSED*/
- static void
- mode_cb(FL_OBJECT * ob, long q)
- {
- immediate = fl_get_choice(ob) - 1;
- }
-
- /*************************************************************
- * What to do if different color is requested
- *************************************************************/
- static void
- handle_color_change(int c[])
- {
- int i = currentobj - offset;
-
- switch_frame_buffer();
- /* need not change the drawing because it is always in colormap mode */
- mapcolor(bcolor, c[0], c[1], c[2]);
-
- /* take care of bitmaps */
- drawmode(NORMALDRAW);
-
- /* if visible: i is the index, offset the starting point */
- if (i >= 0 && i < totalshown)
- {
- fl_mapcolor(FL_BMCOLOR, c[0], c[1], c[2]);
- fl_redraw_object(bms[i]);
- }
- }
-
- /*************************************************************
- * Do this when color change is requested
- ************************************************************/
- /*ARGSUSED */
- static void
- color_cb(FL_OBJECT * ob, long p)
- {
-
- set_getcolor_cb(handle_color_change);
- /* non block */
- get_color(imgptr, dcol, 0);
- }
-
- /**************************************************************
- * Change line thickness: look bad if not line
- *************************************************************/
- /*ARGSUSED*/
- static void
- thickness_cb(FL_OBJECT * ob, long p)
- {
- int status;
-
- do
- {
- status = getint("Enter line thickness", &lwidth, 1, 50, 1);
- set_current_window(win_id);
- switch_frame_buffer();
- color(0);
- cdraw(x, y, w, h, cfill, angle);
- color(bcolor);
- linewidth(lwidth);
- cdraw(x, y, w, h, cfill, angle);
- }
- while (status == 0);
- mark_draw(currentobj, bcolor);
- }
-
- /****************************************************************
- * Change object size: if aspect ratio is to be kept, changing
- * x size should automatically set y size and vice versa
- ****************************************************************/
- static void
- size_cb(FL_OBJECT * ob, long p)
- {
- float sx, sy;
-
- if (p == 0) /* xsize */
- {
- sx = fl_get_slider_value(ob);
- if (xy)
- fl_set_slider_value(sl[1], sy = sx);
- else
- sy = fl_get_slider_value(sl[1]);
- }
- else
- {
- sy = fl_get_slider_value(ob);
- if (xy)
- fl_set_slider_value(sl[!p], sx = sy);
- else
- sx = fl_get_slider_value(sl[!p]);
- }
-
- /* if in user coordinates, convert to pixels */
- if (!pixels)
- {
- w = (sx / mapx + 0.5);
- h = (sy / mapy + 0.5);
- }
- else
- {
- w = (sx + 0.4);
- h = (sy + 0.4);
- }
-
- /* always show it in pixels */
- mark_draw(currentobj, bcolor);
- show_rect_size(w, h);
- }
-
- static void
- report_rotation(float f)
- {
- fl_set_object_label(rtext, ftoa(f, 1));
- }
-
- /*****************************************************
- * get rotation angle in deci-degrees
- *****************************************************/
- /* ARGSUSED */
- static void
- rotate_cb(FL_OBJECT * ob, long q)
- {
-
- while (!get_orientation("Enter Rotation", &angle, 1))
- {
- if (langle - angle)
- {
- mark_draw(currentobj, bcolor);
- }
- }
- fl_set_object_label(rtext, ftoa(0.1 * angle, 1));
- mark_draw(currentobj, bcolor);
- }
-
- /*ARGSUSED*/
- static void
- mark_done(FL_OBJECT * ob, long q)
- {
- fl_qenter(KEYBD, 27);
- }
- /********************************************************************
- * The form
- *******************************************************************/
- static void
- create_form_tobj(void)
- {
-
- FL_OBJECT *obj;
- float xx, dx, yy, dy, x0;
- int i, j, k, ncol;
- static int ok;
-
- if (ok)
- return; /* initialize static variables */
- fl_mapcolor(FL_BMCOLOR, dcol[0], dcol[1], dcol[2]);
-
- switch_frame_buffer();
- mapcolor(bcolor, dcol[0], dcol[1], dcol[2]);
- drawmode(NORMALDRAW);
-
- tobj = fl_bgn_form(FL_NO_BOX, 250.0, 310.0);
- obj = fl_add_box(FL_UP_BOX, 0.0, 0.0, 250.0, 310.0, "");
- obj = fl_add_button(FL_HB, 0.0, 0.0, 250.0, 310.0, "");
- fl_set_call_back(obj, help_cb, HELP_MARKING);
-
- obj = fl_add_box(FL_BORDER_BOX, 10.0, 40.0, 225.0, 110.0, "");
-
-
- /* the origin setting and misc control group */
- fl_bgn_group();
-
- x = 18.0;
- y = 208.0;
- dx = 70.0;
- dy = 23.0;
- obj = fl_add_box(FL_BORDER_BOX, 10.0, 155.0, 228.0, 80.0, "");
- obj = fl_add_button(FL_NB, x, y, dx, dy, "SetOrigin");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_color(obj, FL_MAGIC1, FL_YELLOW);
- fl_set_call_back(obj, origin_cb, 0);
- obj = fl_add_button(FL_NB, x + dx, y, dx, dy, "Rotate");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_color(obj, FL_MAGIC1, FL_YELLOW);
- fl_set_call_back(obj, rotate_cb, 0);
- obj = fl_add_button(FL_PB, x + 2 * dx, y, dx, dy, "DReport");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_color(obj, FL_MAGIC1, FL_YELLOW);
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, dist_cb, 0);
-
- y -= dy + 1;
- otext = obj = fl_add_text(FL_NT, x, y, dx, 20.0, "");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_align(obj, FL_ALIGN_CENTER);
-
- rtext = obj = fl_add_text(FL_NT, x + dx, y, dx, 20.0, "0");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_align(obj, FL_ALIGN_CENTER);
-
- dtext = obj = fl_add_text(FL_NT, x + 2.0 * dx, y, dx, 20.0, "0");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_align(obj, FL_ALIGN_CENTER);
-
- y = 158.0;
- dx = 70;
- dy = 23;
- /* coordinate system to use */
- obj = fl_add_choice(FL_NC, x, y, dx, dy, "");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_choice_fontsize(obj, 10.0);
- fl_addto_choice(obj, "User");
- fl_addto_choice(obj, "Pixels");
- fl_set_choice(obj, pixels + 1);
- fl_set_call_back(obj, misc_cb, 0);
- x += dx;
-
- /* mode of operation */
- obj = fl_add_choice(FL_NC, x, y, dx, dy, "");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_choice_fontsize(obj, 10.0);
- fl_addto_choice(obj, "Deferred");
- fl_addto_choice(obj, "Immediate");
- fl_set_choice(obj, immediate + 1);
- fl_set_call_back(obj, mode_cb, 0);
-
- /* aspect ratio */
- x += dx;
- obj = fl_add_choice(FL_NC, x, y, dx, dy, "");
- fl_set_object_boxtype(obj, FL_ROUNDED_BOX);
- fl_set_choice_fontsize(obj, 10.0);
- fl_addto_choice(obj, "FreeASP");
- fl_addto_choice(obj, "KeepASP");
- fl_set_choice(obj, xy + 1);
- fl_set_call_back(obj, misc_cb, 2);
-
- fl_end_group();
-
- /* input group */
- ingrp = fl_bgn_group();
- ix = obj = fl_add_input(FL_FLOAT_INPUT, 35.0, 70.0, 60.0, 20.0, "X:");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 51);
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, position_cb, 0);
- iy = obj = fl_add_input(FL_FLOAT_INPUT, 35.0, 50.0, 60.0, 20.0, "Y:");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 51);
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, position_cb, 1);
- fl_end_group();
-
- fl_bgn_group();
- mxi = obj = fl_add_input(FL_FLOAT_INPUT, 135.0, 70.0, 70.0, 20.0, "Mx");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 51);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_align(obj, FL_ALIGN_RIGHT);
- fl_set_input(obj, "1.0");
- fl_set_call_back(obj, map_cb, 0);
- myi = obj = fl_add_input(FL_FLOAT_INPUT, 135.0, 50.0, 70.0, 20.0, "My");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 51);
- fl_set_object_lsize(obj, 10.0);
- fl_set_object_align(obj, FL_ALIGN_RIGHT);
- fl_set_input(obj, "1.0");
- fl_set_call_back(obj, map_cb, 1);
-
- obj = fl_add_button(FL_NORMAL_BUTTON, 95.0, 50.0, 40.0, 40.0, "OK");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 9);
- fl_set_button_shortcut(obj, "po");
- fl_set_call_back(obj, doit, 0);
- fl_end_group();
-
- sl[0] = obj = fl_add_valslider(FL_HNS, 15.0, 120.0, 150.0, 20.0, "");
- fl_set_object_boxtype(obj, FL_BORDER_BOX);
- fl_set_object_color(obj, 47, 1);
- fl_set_object_lsize(obj, 10.0);
- fl_set_slider_bounds(obj, 1.0, MAXOSIZE);
- fl_set_slider_step(obj, 1.0);
- fl_set_slider_precision(obj, 0);
- fl_set_slider_value(obj, h);
- fl_set_call_back(obj, size_cb, 0);
- sl[1] = obj = fl_add_valslider(FL_HNS, 15.0, 100.0, 150.0, 20.0, "");
- fl_set_object_boxtype(obj, FL_BORDER_BOX);
- fl_set_object_color(obj, 47, 1);
- fl_set_object_lsize(obj, 10.0);
- fl_set_slider_bounds(obj, 1.0, MAXOSIZE);
- fl_set_slider_step(obj, 1.0);
- fl_set_slider_precision(obj, 0);
- fl_set_slider_value(obj, w);
- fl_set_call_back(obj, size_cb, 1);
-
- obj = fl_add_button(FL_NB, 170.0, 120.0, 60.0, 20.0, "Color");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 4);
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, color_cb, 0);
- obj = fl_add_button(FL_NB, 170.0, 100.0, 60.0, 20.0, "Lwidth");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_object_color(obj, 47, 9);
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, thickness_cb, 0);
- /*
- * The bitmap groups max nine per row, could be seven, depending on
- * totalobjs
- */
- obj = fl_add_box(FL_BORDER_BOX, 8.0, 240.0, 230, 60.0, "");
- if (totalobjs < 18) /* 9 per row */
- ncol = 9;
- else
- {
- ncol = 7;
- obj = fl_add_button(FL_NB, 230 - 40, 230, 45, 55, "More");
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, more_cb, 0);
- }
-
- dx = dy = 25;
- yy = 270.0;
- x0 = xx = 10;
- totalshown = ncol * 2;
- fl_bgn_group();
- for (i = k = 0; i < totalshown; i += ncol, xx = x0, yy -= dy)
- {
- for (j = 0; j < ncol; j++, xx += dx, k++)
- {
- if (k >= totalobjs)
- continue;
- bms[k] = obj = fl_add_bitmap(FL_NBM, xx, yy, dx, dy, "");
- fl_set_object_boxtype(obj, FL_FRAME_BOX);
- fl_set_bitmap(bms[k], BM_W, BM_H, objs[k].bits);
- hb[k] = obj = fl_add_button(FL_HB, xx, yy, dx, dy, "");
- fl_set_call_back(obj, handle_bmcb, k);
- }
- }
- totalshown = k;
- fl_end_group();
- obj = fl_add_button(FL_NB, 10.0, 10.0, 70.0, 25.0, "DelAll");
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, del_dummy, 0);
- obj = fl_add_button(FL_NB, 163.0, 10.0, 70.0, 25.0, "Done");
- fl_set_object_lsize(obj, 10.0);
- fl_set_call_back(obj, mark_done, 0);
- fl_end_form();
- fl_scale_form(tobj, 1.2, 1.1);
- ok = 1;
- }
-